<template>
  <!-- <div> -->
  <div style="position: relative;width: 100%;height:calc(100% - 40px);display: flex;flex-direction: row;padding-top: 40px;">

    <watermark></watermark>

  <div class="left">
  <el-form :model="form" label-width="auto" ref="newFormRef" :rules="newRules"  style="max-width: 600px;padding-top: 30px;">
    <el-form-item label="账&emsp;&emsp;号" prop="account">
      <el-input v-model="form.account" style="width: 200px;"/>
    </el-form-item>
    <el-form-item label="密&emsp;&emsp;码" prop="password">
      <el-input v-model="form.password" style="width: 200px;"/>
    </el-form-item>
    <el-form-item label="姓&emsp;&emsp;名" prop="name">
      <el-input v-model="form.name" style="width: 200px;"/>
    </el-form-item>
    <el-form-item label="头&emsp;&emsp;像" prop="imageUrl">
      <el-upload
        class="avatar-uploader"
        ref="uploadNew"
        action="/api/file/upload"
        :limit="1"
        :show-file-list="false"
        :on-success="handleAvatarSuccess"
        :on-exceed="handleExceedNew"
        :before-upload="isImage"
        accept=".jpg,.jpeg,.png"
      >
        <img v-if="form.imageUrl" :src="form.imageUrl" class="avatar" />
        <el-icon v-else class="avatar-uploader-icon"><Plus /></el-icon>
      </el-upload>
    </el-form-item>
    <el-form-item label="身&emsp;&emsp;份" >
      <el-radio-group v-model="form.state">
        <el-radio :value=1>用户</el-radio>
        <el-radio :value=0>管理员</el-radio>
      </el-radio-group>
    </el-form-item>
    <el-form-item label="性&emsp;&emsp;别">
      <el-radio-group v-model="form.sex">
        <el-radio :value=1>男</el-radio>
        <el-radio :value=0>女</el-radio>
      </el-radio-group>
    </el-form-item>
    <el-form-item label="联系电话" prop="phone">
      <el-input v-model="form.phone" style="width: 200px;"/>
    </el-form-item>
    <el-form-item>
      <el-button type="primary" @click="onSubmit(newFormRef)" style="margin: auto;">提交</el-button>
    </el-form-item>
  </el-form>
</div>

<div class="right">
  <div style="padding: 0.5% 0 0.5% 0;background-color:#EBEEF5;display: flex;flex-direction: row;" >
    <!-- <el-button type="primary"  @click="throttleExportExcel" style="margin-left: 2%;">以生成文件式导出为excel</el-button> -->
    <el-button type="primary" @click="throttleExportExcelStream" style="margin-left: 2%;">以文件流的形式导出为excel</el-button>
    <el-button type="primary" @click="importUserDialog=true">导入用户信息</el-button>
  
  </div>
  
  <el-table :data="userList" stripe style="width: 100%;height: 100%;"
  v-loading="loading"
    element-loading-text="加载中..."
    :element-loading-spinner="svg"
    element-loading-svg-view-box="-10, -10, 50, 50"
    element-loading-background="rgba(122, 122, 122, 0.8)"
  >
    <el-table-column fixed prop="name" label="姓名" align="center"/>
    <el-table-column prop="imageUrl" label="头像" #default="scope" align="center">
      <el-image style="width: 100px; height: 100px" :src="scope.row.imageUrl" />
    </el-table-column>
    <el-table-column prop="account" label="账号" align="center"/>
    <el-table-column prop="password" label="密码" align="center"/>
    <el-table-column label="性别" align="center" #default="scope">
      <span v-if="scope.row.sex==1">男</span>
      <span v-if="scope.row.sex==0">女</span>
      <span v-if="scope.row.sex==10">未知</span>
    </el-table-column>
    <el-table-column prop="phone" label="联系电话" align="center"/> 
    <el-table-column label="权限" align="center" #default="scope">
      <span v-if="scope.row.state==1">用户</span>
      <span v-if="scope.row.state==0">管理员</span>
    </el-table-column>
    <el-table-column prop="createTime" label="创建时间" align="center"/>
    <el-table-column fixed="right" label="" style="">
      <template #default="scope">
        <el-button link type="primary" size="small" @click="edit(scope.row.id)">编辑</el-button>
        <el-button link type="danger" size="small" @click="throttleDeleteId(scope.row.id)">删除</el-button>
        <el-button link><el-link type="primary" :underline="false" :href="scope.row.imageUrl">下载头像</el-link></el-button>
      </template>
    </el-table-column>
  </el-table>
  <div class="page">
        <el-pagination
          :total="total"
          v-model:currentPage="currentPage"
          :page-size="pageSize"
          layout="total,prev,pager,next"
          @current-change="handleCurrentChange"
          />
    </div>
</div>

<el-drawer
    v-model="table"
    title="编辑用户信息"
    direction="ltr"
    size="35%"
    style="min-width: 325px;padding-top: 35px;"
  >
  <div class="editDrawer">
    <el-form :model="editUserList" label-width="auto" ref="editFormRef" :rules="editRules" style="max-width: 600px;padding: 30px;">
      <el-form-item label="账&emsp;&emsp;号" prop="account">
      <el-input v-model="editUserList.account" style="width: 200px;"/>
    </el-form-item>
    <el-form-item label="密&emsp;&emsp;码" prop="password">
      <el-input v-model="editUserList.password" style="width: 200px;"/>
    </el-form-item>
    <el-form-item label="姓&emsp;&emsp;名" prop="name">
      <el-input v-model="editUserList.name" style="width: 200px;"/>
    </el-form-item>
    <el-form-item label="头&emsp;&emsp;像" >
      <el-upload
      ref="uploadEdit"
        class="avatar-uploader"
        action="/api/file/upload"
        :show-file-list="false"
        :on-success="handleUpdateAvatarSuccess"
        :before-upload="isImage" 
        :limit="1"
        accept=".jpeg,.jpg,.png"
        :on-exceed="handleExceedEdit"
      >
        <img v-if="editUserList.imageUrl" :src="editUserList.imageUrl" class="avatar" />
        <el-icon v-else class="avatar-uploader-icon"><Plus /></el-icon>
      </el-upload>
    </el-form-item>
    <el-form-item label="身&emsp;&emsp;份">
      <el-radio-group v-model="editUserList.state">
        <el-radio :value=1>用户</el-radio>
        <el-radio :value=0>管理员</el-radio>
      </el-radio-group>
    </el-form-item>
    <el-form-item label="性&emsp;&emsp;别">
      <el-radio-group v-model="editUserList.sex">
        <el-radio :value=1>男</el-radio>
        <el-radio :value=0>女</el-radio>
      </el-radio-group>
    </el-form-item>
    <el-form-item label="联系电话" prop="phone">
      <el-input v-model="editUserList.phone" style="width: 200px;"/>
    </el-form-item>
      <el-form-item>
      <el-button type="primary" @click="submitEdit(editFormRef)" style="margin: auto;">提交</el-button>
    </el-form-item>
  </el-form>
  </div>

  </el-drawer>

  <el-dialog v-model="importUserDialog" title="导入用户信息" width="400px" >
    <div class="" style="text-align: left;">
        <p class="mb-2x">
          1、第一步：下载导入模板
          <a href="src\assets\用户信息.xls">点击下载模板</a>
        </p>
        <p>2、第二步：在模板上填写信息后，上传文件</p>
      </div>
    <template #footer>
      <div class="dialog-footer" style="display: flex;flex-direction: row;margin-left: 47%;">
        <el-upload ref="upload" action="" :accept="accept" :show-file-list="true" :file-list="fileList" :http-request="myUpload" style="margin-right: 2%;">
          <el-button slot="trigger" type="primary">选择导入的文件</el-button>
        </el-upload>
        <el-button type="primary" @click="importUserDialog = false">
          取消
        </el-button>
      </div>
    </template>
  </el-dialog>
</div>

</template>

<script lang="ts" setup>
import { onUnmounted, ref } from 'vue'
import{reactive} from 'vue'
import { Plus } from '@element-plus/icons-vue'
import  {ElMessage, genFileId} from 'element-plus'
import type { UploadProps,FormInstance,FormRules,ElMessageBox,UploadUserFile, UploadInstance, UploadRawFile} from 'element-plus'
import { addUser,getUserListAPI,deleteByIdAPI,getEditUserAPI,submitEditUserAPI, } from '../../api/user'
import {exportExcelAPI, exportExcelStreamAPI,deleteFileAPI} from '../../api/common'
import {importExcelAPI} from '../../api/common'
import { onMounted } from 'vue'
import useCounter from '../../stores/pinia'
import { useTokenStore } from '../../utils/token'
import watermark from '../../components/modules/watermark.vue'
import { parseJwt } from '../../stores/pinia';

const counterStore=useCounter()
const tokenStore=useTokenStore()
const total=ref(0)
const currentPage=ref(1)
const pageSize=ref(10)
const loading=ref(false)
const svg = `
        <path class="path" d="
          M 30 15
          L 28 17
          M 25.61 25.61
          A 15 15, 0, 0, 1, 15 30
          A 15 15, 0, 1, 1, 27.99 7.5
          L 15 15
        " style="stroke-width: 4px; fill: rgba(0, 0, 0, 0)"/>
        `
const form=ref({
  account:'',
  password:'',
  name:'',
  imageUrl:'',
  createTime:'',
  sex:1,
  phone:'',
  state:1,
})

const userList = ref([
// {id:1,name:'木二支',createTime:'2222',imageUrl:'1111'},
// {id:2,name:'木二支',createTime:'2222',imageUrl:'1111'},
// {id:3,name:'木二支',createTime:'2222',imageUrl:'1111'},
// {id:4,name:'木二支',createTime:'2222',imageUrl:'1111'},
// {id:5,name:'木二支',createTime:'2222',imageUrl:'1111'},
// {id:6,name:'木二支',createTime:'2222',imageUrl:'1111'},
// {id:7,name:'木二支',createTime:'2222',imageUrl:'1111'},
])
const editUserList=ref({
  // name:'dd',
  // imageUrl:'aa'
})

//节流函数
const throttle = (fn, t) => {
  let timer = null;
  return function (...args) {
    if (!timer) {
      timer = setTimeout(() => {
        fn.apply(this, args);
        timer = null;
      }, t);
    }
  };
};

const importUserDialog = ref(false)

// 定义响应式数据
const fileList = ref<UploadUserFile[]>([])
const accept = ref<string>('.xls,.xlsx')

// 自定义上传函数
const myUpload = async (data: any) => {
  fileList.value = [] // 清空文件列表
  const ext = data.file.name.substring(data.file.name.lastIndexOf(".")).toLowerCase();
  const isExt = accept.value.split(",").includes(ext);
  if (!isExt) {
    ElMessage.warning(`选择的文件格式不支持，仅支持：${accept.value}格式`);
    return;
  }

  const formData = new FormData();
  formData.append("file", data.file);

  try {
    const response = await importExcelAPI(formData);
    if (response.data.code === 200) {
      ElMessage.success("导入成功");
      getUserList()
      // 假设这里有其他逻辑，比如刷新列表等
    } else {
      ElMessage.error("导入失败，请稍后再试");
    }
  } catch (error) {
    console.error('导入过程中发生错误:', error);
    ElMessage.error("导入过程中发生错误");
  }
  importUserDialog.value=false
}


// 获取当前时间
const currentTime=()=>{
  var date=new Date();
  var year=date.getFullYear();
  let month=date.getMonth();
  var dateArr=[
    date.getMonth()+1,
    date.getDate(),
    date.getHours(),
    date.getMinutes(),
    date.getSeconds(),
  ];
  // 设置MM,SS
  for(var i=0;i<dateArr.length;i++){
    if(dateArr[i]>=1&&dateArr[i]<=9){
      dateArr[i] ="0"+dateArr[i];
    }
  }
  var strDate=year +"-"+dateArr[0]+"-"+dateArr[1]+" "+dateArr[2]+":"+dateArr[3]+":"+dateArr[4];
  form.value.createTime=strDate
}
//重置新增表单
const resetNew=()=>{
  form.value={
    
    name:'',
    imageUrl:'',
    createTime:'',
    sex:1,
    phone:'',
    state:1,
  }
}
// 提交新增
const onSubmit=async(formEl:FormInstance|undefined)=>{
  newAccount.value=''
  if(!formEl){
    return
  }
  formEl.validate(async(valid)=>{ 
    if(valid){
      currentTime()
  const result=await addUser(form.value)
      // getUserList()
      if(result.data.code!=200){
        newAccount.value=result.data.msg
        
        console.log("sdadadas",newAccount.value)
        formEl.validate()
      }
      if(result.data.code===200){
          getUserList()
          resetNew()
      }
    }
  })
  
  // console.log("返回的数据",result)
}

// 新增检验
const newAccount=ref()

const newFormRef=ref<FormInstance>()
const validateNewAccount=(rule:any,value:any,callback:any)=>{
  if(value===''){
		callback(new Error('请输入账号'))
	}else if(!/^\d+$/.test(value)){
		callback(new Error('请输入纯数字账号'))
	}else if(newAccount.value==='该账号已存在，请换一个'){
		callback(new Error(newAccount.value))
	}else{
		callback()
	}
}
const validateNewName=(rule:any,value:any,callback:any)=>{
	if(value===''){
		callback(new Error('请输入姓名'))
	}else{
		callback()
	}
}
const validateNewImageUrl=(rule:any,value:any,callback:any)=>{
	if(value===''){
		callback(new Error('请输入头像'))
	}else{
		callback()
	}
}
const validateNewPhone=(rule:any,value:any,callback:any)=>{
	if(value===''){
		callback(new Error('请输入手机号'))
	}else{
		callback()
	}
}
const validateNewPassword=(rule:any,value:any,callback:any)=>{
	if(value===''){
		callback(new Error('请输入密码'))
	}else{
		callback()
	}
}
const newRules=reactive<FormRules<typeof editUserList>>({
  account:[{validator:validateNewAccount,trigger:'blur'}],
  password:[{validator:validateNewPassword,trigger:'blur'}],
  name:[{validator:validateNewName,trigger:'blur'}],
  imageUrl:[{validator:validateNewImageUrl,trigger:'blur'}],
  phone:[{validator:validateNewPhone,trigger:'blur'}],
})



//提交修改
const submitEdit=async(formEl:FormInstance|undefined)=>{
  // console.log("提交修改",editUserList.value)
  editAccount.value=''
  if(!formEl){
    return
  }
  formEl.validate(async(valid)=>{
    if(valid){
      const result=await submitEditUserAPI(editUserList.value)
      // getUserList()
      if(result.data.code!=200){
        editAccount.value=result.data.msg
        
        console.log("sdadadas",editAccount.value)
        formEl.validate()
      }
      if(result.data.code===200){
        console.log(result.data)
        if(parseJwt(counterStore.jwt).id==parseJwt(result.data.data).id){
          counterStore.jwt=result.data.data
          location.reload();
        }
        getUserList()
        table.value=false
      }
    }
  })
}

// 修改编辑校验
const editAccount=ref()

const editFormRef=ref<FormInstance>()
const validateEditAccount=(rule:any,value:any,callback:any)=>{
  if(value===''){
		callback(new Error('请输入账号'))
	}else if(!/^\d+$/.test(value)){
		callback(new Error('请输入纯数字账号'))
	}else if(editAccount.value==='该账号已存在，请换一个'){
		callback(new Error(editAccount.value))
	}else{
		callback()
	}
}
const validateEditName=(rule:any,value:any,callback:any)=>{
	if(value===''){
		callback(new Error('请输入姓名'))
	}else{
		callback()
	}
}
const validateEditPhone=(rule:any,value:any,callback:any)=>{
	if(value===''){
		callback(new Error('请输入手机号'))
	}else{
		callback()
	}
}
const validateEditPassword=(rule:any,value:any,callback:any)=>{
	if(value===''){
		callback(new Error('请输入密码'))
	}else{
		callback()
	}
}
const editRules=reactive<FormRules<typeof editUserList>>({
  account:[{validator:validateEditAccount,trigger:'blur'}],
  password:[{validator:validateEditPassword,trigger:'blur'}],
  name:[{validator:validateEditName,trigger:'blur'}],
  phone:[{validator:validateEditPhone,trigger:'blur'}],
})


const handleAvatarSuccess: UploadProps['onSuccess'] = (
  response,//后端存到oss返回的url
  uploadFile//临时的url
) => {
  // form.value.imageUrl = URL.createObjectURL(uploadFile.raw!)
  form.value.imageUrl = response.data;
  console.log("上传的图片地址",form.value.imageUrl)
}


const uploadNew = ref<UploadInstance>()
const handleExceedNew: UploadProps['onExceed'] = async(files) => {
  // console.log(videoUrl.value)
  await deleteFileAPI(form.value.imageUrl)
  uploadNew.value!.clearFiles()
  const file = files[0] as UploadRawFile
  file.uid = genFileId()
  uploadNew.value!.handleStart(file)
  
  uploadNew.value!.submit()
}


const handleUpdateAvatarSuccess: UploadProps['onSuccess'] = (
  response,
  uploadFile
) => {
  // editUserList.value.imageUrl = URL.createObjectURL(uploadFile.raw!)
  editUserList.value.imageUrl=response.data;
  // console.log("上传的图片地址",editUserList.value.imageUrl)
}

const uploadEdit = ref<UploadInstance>()
const handleExceedEdit: UploadProps['onExceed'] = async(files) => {
  // console.log(videoUrl.value)
  await deleteFileAPI(editUserList.value.imageUrl)
  uploadEdit.value!.clearFiles()
  const file = files[0] as UploadRawFile
  file.uid = genFileId()
  uploadEdit.value!.handleStart(file)
  uploadEdit.value!.submit()
}

const isImage: UploadProps['beforeUpload'] = (rawFile) => {
  const isCorrectExtension = rawFile.name.endsWith('.jpg') || rawFile.name.endsWith('.png')||rawFile.name.endsWith('.jpeg');
  if (!isCorrectExtension) {
    ElMessage.error('只能上传jpg或png格式的图片')
    return false
  } else if (rawFile.size / 1024/512 > 1.5) {
    ElMessage.error('图片大小不能超过1MB!')
    return false
  }
  return true
}
const table=ref(false)
const edit=async(id)=>{
  // console.log(id,'编辑')
  const result=await getEditUserAPI(id)
  editUserList.value=result.data.data
  table.value=true
  // console.log("编辑",result)
}

const deleteId=async(id)=>{
  console.log(id,'删除')
  console.log("当前用户id",counterStore.userId)
  const result =await deleteByIdAPI(id)
  if(result.data.code==200){
    ElMessage.success("删除成功！")
    await getUserList()
    setTimeout(() => {
      if(id==counterStore.userId){
      ElMessage.error('登录已过期，请重新登录')
      tokenStore.removeToken()
      counterStore.jwt=""
    }
    }, 1500);
  }
  // console.log("删除",result)
}
const throttleDeleteId=throttle(deleteId,300)


const handleCurrentChange=()=>{
  // console.log("当前页数",currentPage.value)
  getUserList()
}
const getUserList=async()=>{
  let params={
  page:currentPage.value,
  pageSize:pageSize.value
}
  const result=await getUserListAPI(params)
  userList.value=result.data.data.rows
  total.value=result.data.data.total
  // console.log("获取的用户列表",result.data.data.rows)
}
onMounted(()=>{
  getUserList()
})



//生成文件式导出
const exportExcel=async()=>{
  console.log("导出所有数据excel")
  const result=await exportExcelAPI()
  if(result.data.code==200){
    ElMessage.success('已成功导出文件到桌面')
  }
  console.log("导出",result)
}
const throttleExportExcel=throttle(exportExcel,1000)
//文件流式导出
const exportExcelStream=async()=>{
  // console.log("以流的形式导出文件")
  const result=await exportExcelStreamAPI()
  console.log("后端传过来的流",result.data)
  const blob = new Blob([result.data], { type: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet' });
  const url = window.URL.createObjectURL(blob);
  const a = document.createElement('a');
  a.href = url;
  a.download = '用户信息.xlsx'; // 设置下载文件名
  a.click();
  window.URL.revokeObjectURL(url); // 清理 URL
}
const throttleExportExcelStream=throttle(exportExcelStream,1000)

</script>

<style scoped>
  .avatar-uploader{
    background-color: rgb(255, 255, 255);
  }
  .avatar-uploader .avatar {
    width: 178px;
    height: 178px;
    display: block;
  }

  .avatar-uploader .el-upload {
    border: 1px dashed var(--el-border-color);
    border-radius: 6px;
    cursor: pointer;
    position: relative;
    overflow: hidden;
    transition: var(--el-transition-duration-fast);
  }

  .avatar-uploader .el-upload:hover {
    border-color: var(--el-color-primary);
  }

  .el-icon.avatar-uploader-icon {
    font-size: 28px;
    color: #8c939d;
    width: 178px;
    height: 178px;
    text-align: center;
  }
  .left{
    width: 35%;
    height: 100%;
    min-width: 286px;
    float: left;
    display: flex;
    flex-direction: row;
    align-items: center;
    justify-content: center;
    background-color: #f7f7f7;
  }
  .right{
    float: left;
    display: flex;
    flex-direction: column;
    box-shadow: -5px 5px 12px rgba(0,0,0,0.12);
    width: 65%;
    height: 100%;
    /* background-color: #8c939d; */
  }
  .editDrawer{
    width: 100%;
    height: 100%;
    display: flex;
    flex-direction: row;
    align-items: center;
    justify-content: center;
  }
  .page{
    width: 100%;
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    margin-top: auto;
    /* margin-bottom: 1%; */
  }
  /* :deep(.btn-prev){
    height: 1em;
  }
  :deep(.number){
    height: 1em;
  }
  :deep(.btn-next.is-last){
    height: 1em;
  }
  :deep(.el-pagination){
    height: 1em;
  }
  :deep(.more.btn-quickprev.el-icon){
    height: 1em;
  }
  :deep(.more.btn-quicknext.el-icon){
    height: 1em;
  } */
</style>
